"""
在实际项目中，文档会比较大，如果不进行拆分，将所有文档交给LLM大模型，非常浪费TOKEN，且会造成幻觉。
有效的解决方案就是将完整的文档对象进行分块处理。无论是存储还是检索，都将以块作为基本单位。
"""
from langchain_community.document_loaders import TextLoader
from langchain_text_splitters import CharacterTextSplitter, RecursiveCharacterTextSplitter


#characterTextSplitter : Split by character   根据字符数分割
# chunk_size : 每个切块最大TOKEN数量 默认4000
# chunk_overlap : 相邻两个切块之间最大TOKEN数量，默认200
# separator : 切块的分隔符，默认"\n\n"
# length_function: 用于计算切块长度的方法。默认使用父类的TextSplitter的len函数

def fun_1():
    text = """
    LangChain 是一个开源的 Python 库，用于构建 LLM 应用。
    LangChain 允许用户使用 LLM 构建各种应用，如问答系统、内容生成、决策支持、数据处理等。
    LangChain 提供了丰富的工具和组件，使得用户能够轻松地构建自己的 LLM 应用。
    """

    splitter = CharacterTextSplitter(
        chunk_size=50
        , chunk_overlap=10
        , separator="" #设置为空字符串，表示禁用分隔符
    )

    texts = splitter.split_text(text)

    for i , chunk in enumerate(texts): # enumerate() 函数用于将一个可遍历的数据对象组合为一个索引序列，同时列出数据对象。
        print(f"Chunk {i}: {chunk}")

#fun_1()

#最常用的分割器
#RecursiveCharacterTextSplitter 递归字符文本切分器
# 特点，保留上下文，减少碎片化，智能分段，通过递归分隔符将文本分割接近chunk_size的片段大小，支持多种文本类型

def fun_2():
    text = """
    LangChain 是一个开源的 Python 库，用于构建 LLM 应用。\n\nLangChain 允许用户使用 LLM 构建各种应用，如问答系统、内容生成、决策支持、数据处理等。\n\nLangChain 提供了丰富的工具和组件，使得用户能够轻松地构建自己的 LLM 应用。
    """

    splitter = RecursiveCharacterTextSplitter(
        chunk_size=10
        , chunk_overlap=0
    )

    texts = splitter.split_text(text)

    for para in texts:
        print(para)
        print("-" * 20)

#fun_2()

def fun_3():
    text_list = ["LangChain 是一个开源的 Python 库，用于构建 LLM 应用。\n\nLangChain 允许用户使用 LLM 构建各种应用，如问答系统、内容生成、决策支持、数据处理等。\n\nLangChain 提供了丰富的工具和组件，使得用户能够轻松地构建自己的 LLM 应用。"]


    splitter = RecursiveCharacterTextSplitter(
        chunk_size=10
        , chunk_overlap=0
        , add_start_index= True # 是否添加起始索引，只有分割document对象才有效果
    )

    texts = splitter.create_documents(text_list) #create_documents用于处理列表中的文本,返回的是Document对象列表

    for para in texts:
        print(para)
        print("-" * 20)

#fun_3()

#加载本地文件
def fun_4():

    with open("F:\\data\\1.txt", "r" , encoding="utf-8") as f:
        file_content = f.read()

    splitter = RecursiveCharacterTextSplitter(
        chunk_size=100
        , chunk_overlap=20
        , length_function=len
    )

    texts = splitter.create_documents([file_content])

    for document in texts:
        print(document.page_content)
        print("-" * 20)

#fun_4()

#使用文档加载器
def fun_5():
    loader = TextLoader(file_path="F:/data/1.txt", encoding="utf-8")
    documents = loader.load()

    splitter = RecursiveCharacterTextSplitter(
        chunk_size=100
        , chunk_overlap=20
        , length_function=len
    )

    texts = splitter.split_documents(documents)

    for document in texts:
        print(document.page_content)
        print("-" * 20)

#fun_5()

#添加自定义分隔符
def fun_6():
    loader = TextLoader(file_path="F:/data/1.txt", encoding="utf-8")
    documents = loader.load()

    splitter = RecursiveCharacterTextSplitter(
        chunk_size=100
        , chunk_overlap=20
        , length_function=len
        , separators=["\n\n", "\n", "。 ",  "!" , "?","……", ""]
        , keep_separator= True # 保留句尾标点符号，避免切割后失去语气和逻辑
    )

    texts = splitter.split_documents(documents)

    for document in texts:
        print(document.page_content)
        print("-" * 20)

fun_6()